package com.design.reactor.stretchIO._3_multiReactorMultiThread_destroy;

import java.io.IOException;
import java.net.InetSocketAddress;
import java.nio.channels.SelectionKey;
import java.nio.channels.Selector;
import java.nio.channels.ServerSocketChannel;
import java.nio.channels.SocketChannel;
import java.util.Iterator;
import java.util.Set;

public class Reactor3  implements Runnable{
	final Selector[] selectors=new Selector[2];
	int next = 0;
    final ServerSocketChannel serverSocketChannel;

    /**
     * reactor 1: 初始设置
     */
    Reactor3(int port) throws IOException {
    	selectors[0]=Selector.open();
        selectors[1]= Selector.open();
        serverSocketChannel = ServerSocketChannel.open();
        serverSocketChannel.socket().bind(new InetSocketAddress(port));
        serverSocketChannel.configureBlocking(false);
        SelectionKey sk = serverSocketChannel.register(selectors[0], SelectionKey.OP_ACCEPT);
        Acceptor acceptor= new Acceptor();
        sk.attach(acceptor);//绑定数据
        System.out.println("----Reactor 构造函数 中ServerSocketChannel  SelectionKey ： " + sk);
        System.out.println("----Reactor 构造函数 中绑定的 对象   acceptor ： " + acceptor);
    }
    /**
     * reactor 2: 分发循环
     */
    @Override
    public void run() {
        try {

        	System.out.println("----当前线程名 ："+Thread.currentThread().getName());
            while (!Thread.interrupted()) {
                for (Selector selector : selectors) {
                    selector.select();//获取注册事件
                    Set<SelectionKey> sks = selector.selectedKeys();
                    for (SelectionKey sk : sks) {
                        dispatcher(sk);//分发每一个请求
                    }
                    // 也可以在while循环中使用iterator的remove方法
                    sks.clear();
                }
            }
        } catch (IOException ignored) {
            // ignored
        }
    }

    private void dispatcher(SelectionKey sk) {

        Runnable r = (Runnable) sk.attachment();//获取之前绑定的对象
        if (null != r) {
            r.run();
        }
    }
    //Acceport也是处理器EventHandler的一种, 用于处理socket accept事件
    class Acceptor implements Runnable {
        @Override
        public void run() {
            try {
            	//Socket connection = serverSocket.accept();
            	System.out.println("----当前线程名 ："+Thread.currentThread().getName());

                SocketChannel c = serverSocketChannel.accept();
                System.out.println("----Acceptor  run() 中  获得的客户端SocketChannel ： " + c);
                //选个subReactor去负责接收到的connection
                if (null != c)  new Handler3(selectors[1], c);
//                if (null != c)  new Handler3(selectors[next], c);
//                if (++next == selectors.length) next = 0;

            } catch (IOException ignored) {
                // ignored
            }
        }
    }
    public static void main(String[] args) throws Exception {
    	Reactor3 reactor= new Reactor3(8899);
    	new Thread(reactor).start();//这就是 reactor 线程 服务端线程
	}
}
